<?php

namespace App\Http\Validate\OpenShop\InvestmentPromotion;

use App\Enums\OpenShop\InvestmentPromotion\SignOrderEnum;
use App\Enums\OpenShop\InvestmentPromotion\UserBaseInfoEnum;
use App\Enums\OpenShop\InvestmentPromotion\UserOrderEnum;
use App\Http\Validate\BaseValidate;
use App\Models\OpenShop\InvestmentPromotion\OpenShopSignOrderModel;
use App\Models\OpenShop\InvestmentPromotion\OpenShopUserBaseInfoModel;
use App\Models\OpenShop\InvestmentPromotion\OpenShopUserContractModel;
use App\Models\OpenShop\SiteLocation\OpenShopSiteLocationModel;
use App\Service\OpenShop\Feishu\ConfigService;
use Illuminate\Support\Facades\Validator;
use Illuminate\Validation\Rule;
use Illuminate\Validation\ValidationException;


/**
 * [ open_shop_user_base_info 招商加盟 - 用户基础信息 ] - 校验规则
 *
 * @UserBaseInfoValidate
 * @package App\Http\Controllers
 * @date 2022/02/28 06:48:03
 * @author GreenLeaf <786407418@qq.com>
 */
class UserBaseInfoValidate extends BaseValidate
{

    /**
     * 注册校验规则
     */
    public static function registerValidateRules(): void
    {
        Validator::extend('mobile', function ($attribute, $value, $parameters, $validator) {
            return $validator->validateRegex(
                $attribute,
                $value,
                ['/^1\d{10}$/'],
                "手机号格式非法"
            );
        });
    }

    /**
     * 预处理参数
     *
     * @param array $data
     * @return array
     */
    public static function beforeValidate(array $data): array
    {
        $data = collect($data)->filter(function ($v, $k) {

            if ($v === "" && !in_array($k, [
                    "shopBudget",
                    "remarkMobile1",
                    "remarkMobile2",
                    "postCode",
                    "shopCityCode",
                    "shopDistrictCode",
                    "chooseShopCityCode",
                    "chooseShopDistrictCode",
                    "cardAccountName",
                    "cardBankName",
                    "cardNo",
                ])) {
                return false;
            }
            return true;
        })->toArray();
        return parent::beforeValidate($data); // TODO: Change the autogenerated stub
    }

    /**
     * 获取规则信息
     *
     * @param array $fields
     * @return string[]
     */
    public static function getRules(array $fields = []): array
    {
        return self::getActuallyRules([
            'orderNo'                 => 'bail|required|exists:' . OpenShopUserBaseInfoModel::class . ',OrderNo',
            //
            'mobile'                  => 'bail|required|string|mobile',
            //招商加盟注册手机号
            'remarkMobile1'           => 'sometimes|string|max:36',
            //招商加盟备注手机号——1
            'remarkMobile2'           => 'sometimes|string|max:36',
            //招商加盟备注手机号--2
            'email'                   => 'required|string|email|max:120',
            'weChatNumber'            => 'required|string|max:120',
            //微信号
            'isMarried'               => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["isMarried"])
                    ->pluck("name", "id")->toArray()),
            //是否已婚 0:未婚 1:已婚
            'provinceCode'            => 'required|string|max:12',
            //省份code
            'cityCode'                => 'required|string|max:12',
            //市级code
            'districtCode'            => 'required|string|max:12',
            //区域code
            'address'                 => 'required|string|max:60',
            //详细地址信息
            'addressPrefix'           => 'required|string',
            //详细地址信息
            'postCode'                => 'sometimes|string|max:12',
            //邮编
            'source'                  => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["source"])
                    ->pluck("name", "id")->toArray()),
            //来源渠道 - 0 : 微信公众号1 : 百度竞价2 : 自主招商
            'isSelfManaged'           => 'sometimes|required|in:' . enumTransToRules(UserBaseInfoEnum::IS_SELF_MANAGED),
            //是否亲自经营 - 0 : 否1 : 是
            'joinReason'              => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["joinReason"])
                    ->pluck("name", "id")->toArray()),
            //加盟原因 - 0 : 品牌影响力大1 : 朋友推荐2 : 产品好吃
            'shopBudget'              => 'sometimes|integer|max:9999999',
            //开店预算
            'investmentMode'          => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["investmentMode"])
                    ->pluck("name", "id")->toArray()),
            //投资方式 - 0 : 公司1 : 个人2 : 合伙3 : 委托4 : 其他
            'financeSource'           => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["financeSource"])
                    ->pluck("name", "id")->toArray()),
            //资金来源 - 0 : 自有1 : 自筹2 : 贷款3 : 合资4 : 其他
            'isSelfWithAddress'       => 'sometimes|required|in:' . enumTransToRules(UserBaseInfoEnum::IS_SELF_WITH_ADDRESS),
            'clueNo'                  => [
                'sometimes',
                'string',
                Rule::exists("open_shop_site_locations", "orderNo")
                    ->where("source", OpenShopSiteLocationModel::SOURCE_HOUSING)
                    ->where("clueStatus", OpenShopSiteLocationModel::CLUE_STATUS_5)
            ],
            //是否自带选址 - 0 : 否1 : 是
            'shopProvinceCode'        => 'exclude_unless:isSelfWithAddress,' . UserBaseInfoEnum::SELF_WITH_ADDRESS . '|required|string|max:12',
            //门店省份code
            'shopCityCode'            => 'exclude_unless:isSelfWithAddress,' . UserBaseInfoEnum::SELF_WITH_ADDRESS . '|sometimes|string|max:12',
            //门店市级code
            'shopDistrictCode'        => 'exclude_unless:isSelfWithAddress,' . UserBaseInfoEnum::SELF_WITH_ADDRESS . '|sometimes|string|max:12',
            //门店区域code
            'shopAddressPrefix'       => 'exclude_unless:isSelfWithAddress,' . UserBaseInfoEnum::SELF_WITH_ADDRESS . '|required|string',
            'shopAddress'             => 'exclude_unless:isSelfWithAddress,' . UserBaseInfoEnum::SELF_WITH_ADDRESS . '|required|string|max:120',
            'shopName'                => 'sometimes|string|max:48',
            //详细地址信息
            'chooseAddressReason'     => 'sometimes|required|in:' . enumTransToRules(collect(ConfigService::config("openShop")["chooseAddressReason"])
                    ->pluck("name", "id")->toArray()),
            //选址原因 - 0 : 人流量大1 : 房租便宜2 : 不要房租
            'chooseShopProvinceCode'  => 'required|string|max:12',
            //门店省份code
            'chooseShopCityCode'      => 'sometimes|string|max:12',
            //门店市级code
            'chooseShopDistrictCode'  => 'sometimes|string|max:12',
            //门店区域code
            'chooseShopAddressPrefix' => 'required|string|max:120',

            // 银行卡号
            "cardNo"                  => 'required',
            // 银行开户行
            "cardBankName"            => 'required',
            // 银行账户名称
            "cardAccountName"         => 'required'
        ], $fields);
    }

    /**
     * @var array|string[]
     */
    public static array $validateMsg = [
        'mobile.mobile'        => '手机号不合法',
        'remarkMobile1.mobile' => '手机号不合法',
        'remarkMobile2.mobile' => '手机号不合法',
    ];

    /**
     * @var array|string[]
     */
    public static array $attributes = [
        'orderNo'             => '订单号',
        'mobile'              => '手机号码',
        'remarkMobile1'       => '备选手机号码 - 1',
        'remarkMobile2'       => '备选手机号码 - 2',
        'email'               => '邮箱',
        'weChatNumber'        => '微信号',
        'isMarried'           => '是否已婚',
        'provinceCode'        => '省份code',
        'cityCode'            => '市级code',
        'districtCode'        => '区域code',
        'address'             => '详细地址信息',
        'addressPrefix'       => '详细地址信息 - 省市区',
        'postCode'            => '邮编',
        'source'              => '来源渠道',
        'isSelfManaged'       => '是否亲自经营',
        'joinReason'          => '加盟原因',
        'shopBudget'          => '开店预算',
        'investmentMode'      => '投资方式',
        'financeSource'       => '资金来源',
        'shopProvinceCode'    => '门店省份code',
        'shopCityCode'        => '门店市级code',
        'shopDistrictCode'    => '门店区域code',
        'shopAddressPrefix'   => '详细地址信息',
        'shopAddress'         => '门店地址',
        'shopName'            => '门店名称',
        'isSelfWithAddress'   => '是否自带选址',
        'clueNo'              => "房源编号",
        'chooseAddressReason' => '选址原因',

        'chooseShopProvinceCode'  => '门店选址省份code',
        'chooseShopCityCode'      => '门店选址市级code',
        'chooseShopDistrictCode'  => '门店选址区域code',
        'chooseShopAddressPrefix' => '门店选址详细地址信息',

        "cardNo"          => '银行账号',
        "cardBankName"    => '银行卡开户行',
        "cardAccountName" => '银行卡账户名称'
    ];

    /**
     * 创建校验
     *
     * @param array $requestParams
     * @return array
     * @throws ValidationException
     */
    public static function insertValidate(array $requestParams): array
    {
        return self::baseValidate(
            $requestParams,
            collect(self::getRules())->except(['orderNo'])->keys()->toArray(),
            function (array $params) {
                if (empty($params["shopBudget"])) {
                    $params["shopBudget"] = 0;
                }
                return $params;
            },
            null,
            self::getValidateMsg()
        );
    }

    /**
     * 更新校验
     *
     * @param array $requestParams
     * @return array
     * @throws ValidationException
     */
    public static function updateValidate(array $requestParams): array
    {
        $userContract = OpenShopUserContractModel::query()
                                                 ->where("orderNo", $requestParams["orderNo"] ?? "")
                                                 ->first();

        $signOrder = OpenShopSignOrderModel::query()
                                           ->where("orderNo", $requestParams["orderNo"] ?? "")
                                           ->first();

        $validateFields =
//            (($signOrder && $signOrder->step >= SignOrderEnum::STEP_3) ?
//            [
//                "remarkMobile1",
//                "remarkMobile2",
//                "isMarried",
//                "postCode",
//                "orderNo",
//                "source",
//                "isSelfManaged",
//                "joinReason",
//                "shopBudget",
//                "investmentMode",
//                "financeSource",
//                "isSelfWithAddress",
//                "shopName",
//                "chooseAddressReason",
//                "cardNo",
//                "cardBankName",
//                "cardAccountName",
//                "weChatNumber",
//                "postCode",
//                "address",
//                "addressPrefix",
//                "districtCode",
//                "cityCode",
//                "provinceCode",
//                "email"
//            ] :
            array_keys(self::getRules());


        return self::baseValidate(
            $requestParams,
            array_merge($validateFields, ($userContract && $userContract->exceptionMsg) ? ["mobile"] : []),
            function (array $params) {
                if (empty($params["shopBudget"])) {
                    $params["shopBudget"] = 0;
                }

                if (isset($params["isSelfWithAddress"]) && $params["isSelfWithAddress"] == UserBaseInfoEnum::SELF_WITHOUT_ADDRESS) {
                    $params["shopProvinceCode"]    = "";
                    $params["shopCityCode"]        = "";
                    $params["shopDistrictCode"]    = "";
                    $params["shopAddressPrefix"]   = "";
                    $params["chooseAddressReason"] = 0;
                    $params["shopAddress"]         = "";
                    $params["shopName"]            = "";
                    $params["clueNo"]              = "";
                    $params["clueNo"]              = "";
                }

                return $params;
            },
            null,
            self::getValidateMsg()
        );
    }


    /**
     * @param array $requestParams
     * @return array
     * @throws ValidationException
     */
    public static function detailValidate(array $requestParams): array
    {
        return self::baseValidate($requestParams, ['orderNo']);
    }

    /**
     * @param array $requestParams
     * @return array
     * @throws ValidationException
     */
    public static function orderBaseInfoUpdateValidate(array $requestParams): array
    {
        return self::baseValidate(
            $requestParams,
            [
                "shopProvinceCode",
                "shopCityCode",
                "shopDistrictCode",
                "shopAddressPrefix",
                "chooseAddressReason",
                "isSelfWithAddress",
                "chooseShopProvinceCode",
                "chooseShopCityCode",
                "chooseShopDistrictCode",
                "chooseShopAddressPrefix",
                "shopName",
                "shopAddress"
            ],
            null,
            null,
            self::$attributes
        );
    }
}
